package band.wukong.practice.netty.nettyinactionessential.ch02;

import band.wukong.practice.netty.Env;
import io.netty.bootstrap.ServerBootstrap;
import io.netty.channel.ChannelFuture;
import io.netty.channel.ChannelInitializer;
import io.netty.channel.EventLoopGroup;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.SocketChannel;
import io.netty.channel.socket.nio.NioServerSocketChannel;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;

import java.net.InetSocketAddress;

/**
 * Desc:
 * author: wukonggg@139.com
 */
public class EchoServer {

    private static final Logger logger;

    static {
        Env.assemblingLog4j2ConfFile();
        logger = LogManager.getLogger(EchoServer.class);
    }

    private final int PORT;

    public EchoServer(int PORT) {
        this.PORT = PORT;   // 1.设置端口值
    }

    /**
     * 2.呼叫服务器的 bind() 方法
     *
     * @throws InterruptedException
     */
    public void start() throws InterruptedException {
        final EventLoopGroup group = new NioEventLoopGroup();   // 3.创建 EventLoopGroup
        try {
            ServerBootstrap b = new ServerBootstrap();
            b.group(group)  // 4.创建 ServerBootstrap
                    .channel(NioServerSocketChannel.class)  // 5.指定使用 NIO 的传输 Channel
                    .localAddress(new InetSocketAddress(PORT)) // 6.设置 socket 地址使用所选的端口
                    .childHandler(
                            // 7.添加 EchoServerHandler 到 Channel 的 ChannelPipeline
                            new ChannelInitializer<SocketChannel>() {
                                @Override
                                protected void initChannel(SocketChannel socketChannel) throws Exception {
                                    socketChannel.pipeline().addLast(new EchoServerHandler());
                                }
                            });
            ChannelFuture f = b.bind().sync();  // 8.绑定的服务器，sync 等待服务器关闭
            f.channel().closeFuture().sync();   // 9.关闭 channel 和 块，直到它被关闭

        } finally {
            group.shutdownGracefully().sync();  // 10.关机的 EventLoopGroup，释放所有资源。
        }
    }
}
